﻿using Assets.Game.scripts.components;
using Assets.Game.scripts.ui.models;
using Engine.Entities.Character;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using UnityEngine;

namespace Assets.Game.scripts.ui.controllers {

    [RequireComponent(typeof(PartyItemRendererModel))]
    class PartyCouplingWidgetController : MonoBehaviour {

        public UIGrid charactersInPartyTable;
        public UIGrid fatherTable;
        public UIGrid motherTable;
        public GameObject childContainer;

        public GameObject characterInPartyItemRenderer;
        private bool isRefreshRequired;

        private SteveBrain father;
        private SteveBrain mother;
        private GameObject childRenderer = null;

        void Start() {
            PartyItemRendererModel model = this.GetComponent<PartyItemRendererModel>();

            if (model != null && this.charactersInPartyTable != null && this.characterInPartyItemRenderer != null) {
                foreach (SteveBrain character in model.party.PeopleInParty) {
                    SteveModel agentModel = character.model;
                    GameObject itemRendererInstance = NGUITools.AddChild(
                        this.charactersInPartyTable.gameObject,
                        this.characterInPartyItemRenderer
                    );

                    CharacterItemRendererModel item = itemRendererInstance.GetComponent<CharacterItemRendererModel>();
                    if (item != null) {
                        item.data = character;
                    }

                    UIDragDropItemListener dragListener = itemRendererInstance.GetComponent<UIDragDropItemListener>();
                    EventDelegate dragEndCallback = new EventDelegate(this, "onDragEnd");;
                    dragEndCallback.parameters[0].value = itemRendererInstance;
                    dragEndCallback.parameters[1].value = item;
                    EventDelegate dragStartCallback = new EventDelegate(this, "onDragStart"); ;
                    dragStartCallback.parameters[0].value = itemRendererInstance;
                    dragStartCallback.parameters[1].value = item;
                    if (dragListener != null) {
                        EventDelegate.Set(dragListener.onDragEnd, dragEndCallback);
                        EventDelegate.Set(dragListener.onDragStart, dragStartCallback);
                    }
                }
            }

            this.isRefreshRequired = true;
        }

        public void Update() {
            if (this.isRefreshRequired) {
                if (this.charactersInPartyTable != null) {
                    this.charactersInPartyTable.Reposition();
                }
                this.isRefreshRequired = false;
            }
        }

        public void onClose() {
            NGUITools.Destroy(this.gameObject);
        }

        public void onDragStart(GameObject draggedObject, CharacterItemRendererModel characterModel) {
            print("drag started!");
        }

        
        public void onDragEnd(GameObject draggedObject, CharacterItemRendererModel characterModel) {
            GameObject parent = draggedObject.transform.parent.gameObject;
            bool isParentFatherTable = System.Object.ReferenceEquals(parent.transform, this.fatherTable.transform);
            bool isParentMotherTable = System.Object.ReferenceEquals(parent.transform, this.motherTable.transform);

            //controllo che sto inserendo una persona di un dato sesso nella giusta grid
            if ((isParentFatherTable && characterModel.gender == GenderEnum.Male) ||
                (isParentMotherTable && characterModel.gender == GenderEnum.Female)) {

                //se c'è già qualcuno allora lo reinserisco nella grid degli individui della comitiva
                if (parent.transform.childCount > 1) {
                    GameObject child = parent.transform.GetChild(0).gameObject;
                    child.transform.parent = null;
                    this.charactersInPartyTable.AddChild(child.transform);
                }
            }
            else{
                //interrompo il drag e rimetto a posto l'oggetto draggato
                draggedObject.transform.parent = null;
                this.charactersInPartyTable.AddChild(draggedObject.transform);
            }

            //seleziono i genitori
            father = this.fatherTable.transform.childCount == 0 
                ? null
                : this.fatherTable.transform.GetChild(0).GetComponent<CharacterItemRendererModel>().data;

            mother = this.motherTable.transform.childCount == 0
                ? null
                : this.motherTable.transform.GetChild(0).GetComponent<CharacterItemRendererModel>().data;

        }

        public bool CouplingActive
        {
            get
            {
                //attivo il cuore solo se ci sono i genitori e 
                //non ho ancora figliato
                if (father != null && mother != null && childRenderer == null)
                    return true;
                else
                    return false;
            }
        }

        public float AlphaSprite
        {
            get
            {
                return CouplingActive ? 1 : 0; 
            }
        }

        public void Couple()
        {
            if (father == null || mother == null) return;

            //creo un nuovo personaggio
            SteveBrain brain = FrenzyPeopleController.instance.Couple(father.model, mother.model);

            //lo inserisce nel container dei figli
            GameObject itemRendererInstance = NGUITools.AddChild(
                        this.childContainer,
                        this.characterInPartyItemRenderer
                    );

            //assegna il model
            CharacterItemRendererModel item = itemRendererInstance.GetComponent<CharacterItemRendererModel>();
            if (item != null)
            {
                item.data = brain;
            }

            childRenderer = itemRendererInstance;

        }

    }
}
